/**
 * 功能:
 * 作者:周逸健
 * 日期: 2023/10/25 9:01
 */
package com.cgnfz.crm.service.impl;

import com.baomidou.mybatisplus.core.toolkit.Wrappers;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import com.cgnfz.crm.entity.dto.EmployeeInfo;
import com.cgnfz.crm.entity.vo.request.RegisterVO;
import com.cgnfz.crm.mapper.EmployeeMapper;
import com.cgnfz.crm.service.EmployeeService;
import com.cgnfz.crm.utils.Const;
import com.cgnfz.crm.utils.FlowUtils;
import jakarta.annotation.Resource;
import org.springframework.data.redis.core.StringRedisTemplate;
import org.springframework.security.core.userdetails.User;
import org.springframework.security.core.userdetails.UserDetails;
import org.springframework.security.core.userdetails.UsernameNotFoundException;
import org.springframework.security.crypto.password.PasswordEncoder;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import java.util.Date;

@Service
public class EmployeeServiceImpl extends ServiceImpl<EmployeeMapper, EmployeeInfo> implements EmployeeService {


    @Resource
    StringRedisTemplate stringRedisTemplate;

    @Resource
    FlowUtils utils;

    @Resource
    PasswordEncoder passwordEncoder;

    @Override
    public UserDetails loadUserByUsername(String name) throws UsernameNotFoundException {
        EmployeeInfo employeeInfo = this.findAccountByIdOrPhone(name);
        if (employeeInfo == null)
            throw new UsernameNotFoundException("用户名或密码错误");
        return User
                .withUsername(name)
                .password(employeeInfo.getPassword())
                .roles(employeeInfo.getRole())
                .build();
    }

    @Override
    public EmployeeInfo findAccountByIdOrPhone(String text) {
        return this.query()
                .eq("employee_id", text.toUpperCase()).or()
                .eq("phone", text)
                .one();
    }


    /**
     * @return
     */
    @Override
    @Transactional(rollbackFor = Exception.class)
    public String registerAccount(RegisterVO vo) {
        String employeeId = vo.getEmployeeId();
        /*String code = stringRedisTemplate.opsForValue().get(Const.VERIFY_EMAIL_DATA + emploeeId);
        if (code == null) return "请先获取验证码";
        if (!code.equals(vo.getCode())) return "验证码错误，请重新输入";*/
        if (this.existsAccountByEmploeeId(employeeId)) return "该工号已被注册";
        String phone = vo.getPhone();
        if (this.existsAccountByPhone(phone)) return "该手机号已被他人使用，请重新更换";
        String password = passwordEncoder.encode(vo.getPassword());
        EmployeeInfo info = new EmployeeInfo(employeeId.toUpperCase(), vo.getEmployee(), vo.getEmployeeCompany(), password, phone, "01", new Date());
        if (!this.save(info)) {
            return "内部错误，注册失败";
        } else {
            this.deleteEmailVerifyCode(employeeId);
            return null;
        }
    }

    /**
     * @param vo
     * @return
     */
    @Override
    public String resetConfirm(RegisterVO vo) {
        String employeeId = vo.getEmployeeId().toUpperCase();
        String phone = vo.getPhone();
        if (this.checkAccountByPhone(phone, employeeId)) {
            return null;
        } else {
            return "员工号与手机号不匹配，请重新输入";
        }
    }

    @Override
    public String resetPassword(RegisterVO vo) {
        String employeeId = vo.getEmployeeId().toUpperCase();
        String password = passwordEncoder.encode(vo.getPassword());
        boolean update = this.update().eq("employee_id", employeeId).set("password", password).update();
        return update ? null : "更新失败，请联系管理员";

    }


    private void deleteEmailVerifyCode(String employeeId) {
        String key = Const.ATTR_USER_ID + employeeId.toUpperCase();
        stringRedisTemplate.delete(key);
    }

    private boolean existsAccountByPhone(String phone) {
        return this.baseMapper.exists(Wrappers.<EmployeeInfo>query().eq("phone", phone));
    }

    private boolean existsAccountByEmploeeId(String employeeId) {
        return this.baseMapper.exists(Wrappers.<EmployeeInfo>query().eq("employee_id", employeeId));
    }

    private boolean checkAccountByPhone(String phone, String employeeId) {
        return this.baseMapper.exists(Wrappers.<EmployeeInfo>query().eq("phone", phone).eq("employee_id", employeeId));
    }


}
